package com.huffman.smart_picture.api.process;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpUtil;
import cn.hutool.json.JSONUtil;
import com.huffman.smart_picture.api.process.dto.BackgroundProcessDto;
import com.huffman.smart_picture.api.process.dto.IdPhotoProcessDto;
import com.huffman.smart_picture.api.process.dto.MattingProcessDto;
import com.huffman.smart_picture.api.process.dto.WatermarkProcessDto;
import com.huffman.smart_picture.common.exception.BusinessException;
import com.huffman.smart_picture.common.exception.ErrorEnum;
import com.huffman.smart_picture.utils.ThrowUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.io.File;
import java.util.HashMap;
import java.util.Objects;

/**
 * @author DengLin
 * @title 图片处理api
 * @date 2025/5/20
 */
@Component
@Slf4j
public class PictureProcessApi {

    /**
     * 抠图接口名
     */
    private final String HUMAN_MATTING = "human_matting";

    /**
     * 加水印接口名
     */
    private final String WATERMARK = "watermark";

    /**
     * 为图片添加背景颜色
     */
    private final String ADD_BACKGROUND = "add_background";

    /**
     * 将人物照背景透明
     */
    private final String ID_PHOTO = "idphoto";

    @Value("${api.process.id-photo}")
    private String ID_PHOTO_URL_PRE;


    /**
     * 抠图
     *
     * @param mattingProcessDto
     * @return 抠出的人像Base64
     */
    public ProcessResult humanMatting(MattingProcessDto mattingProcessDto) {
        File inputImage = mattingProcessDto.getInputImage();
        Integer dpi = mattingProcessDto.getDpi();
        String mattingModel = mattingProcessDto.getHumanMattingModel();
        ThrowUtil.throwIf(Objects.isNull(inputImage), ErrorEnum.PARAM_EMPTY, "图片为空");

        if (mattingModel == null || StrUtil.isBlank(mattingModel)) {
            mattingModel = "hivision_modnet";
        }
        if (Objects.isNull(dpi)) {
            dpi = 300;
        }

        HashMap<String, Object> paramMap = new HashMap<>();
        paramMap.put("input_image", inputImage);
        paramMap.put("human_matting_model", mattingModel);
        paramMap.put("dpi", dpi);

        ProcessResult processResult;

        String url = ID_PHOTO_URL_PRE + HUMAN_MATTING;

        try {
            String response = HttpUtil.post(url, paramMap);
            processResult = JSONUtil.toBean(response, ProcessResult.class);
        } catch (Exception e) {
            log.error("request fail:{}", e.getMessage());
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "人像抠图失败");
        }

        if (processResult == null || Boolean.FALSE.equals(processResult.isStatus())) {
            log.error("response fail");
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "人像抠图失败");
        }

        return processResult;
    }

    /**
     * 加水印
     *
     * @param watermarkProcessDto
     * @return
     */
    public ProcessResult watermark(WatermarkProcessDto watermarkProcessDto) {

        String text = watermarkProcessDto.getText();
        Integer size = watermarkProcessDto.getSize();
        Float opacity = watermarkProcessDto.getOpacity();
        Integer angle = watermarkProcessDto.getAngle();
        String color = watermarkProcessDto.getColor();
        Integer space = watermarkProcessDto.getSpace();
        File inputImage = watermarkProcessDto.getInputImage();
        String inputImageBase64 = watermarkProcessDto.getInputImageBase64();
        Integer dpi = watermarkProcessDto.getDpi();
        ThrowUtil.throwIf(Objects.isNull(inputImage) && StrUtil.isBlank(inputImageBase64),
                ErrorEnum.UPLOAD_FILE_EMPTY, "图片为空");

        HashMap<String, Object> paramMap = new HashMap<>();
        if (Objects.nonNull(inputImage)) {
            paramMap.put("input_image", inputImage);
        }
        if (StrUtil.isNotBlank(inputImageBase64)) {
            paramMap.put("input_image_base64", inputImageBase64);
        }
        paramMap.put("text", text);
        paramMap.put("size", size);
        paramMap.put("opacity", opacity);
        paramMap.put("angle", angle);
        paramMap.put("color", color);
        paramMap.put("space", space);
        paramMap.put("dpi", dpi);

        ProcessResult processResult;
        String url = ID_PHOTO_URL_PRE + WATERMARK;
        try {
            String response = HttpUtil.post(url, paramMap);
            processResult = JSONUtil.toBean(response, ProcessResult.class);
        } catch (Exception e) {
            log.error("request fail:{}", e.getMessage());
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "水印添加失败");
        }

        if (processResult == null || Boolean.FALSE.equals(processResult.isStatus())) {
            log.error("response fail");
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "水印添加失败");
        }

        return processResult;
    }

    /**
     * 透明证件照
     *
     * @param idPhotoProcessDto
     * @return
     */
    public ProcessResult idPhoto(IdPhotoProcessDto idPhotoProcessDto) {
        Boolean faceAlignment = idPhotoProcessDto.getFaceAlignment();
        Float headMeasureRatio = idPhotoProcessDto.getHeadMeasureRatio();
        Float headHeightRatio = idPhotoProcessDto.getHeadHeightRatio();
        Float topDistanceMax = idPhotoProcessDto.getTopDistanceMax();
        Float topDistanceMin = idPhotoProcessDto.getTopDistanceMin();
        Integer brightnessStrength = idPhotoProcessDto.getBrightnessStrength();
        Integer contrastStrength = idPhotoProcessDto.getContrastStrength();
        Integer sharpenStrength = idPhotoProcessDto.getSharpenStrength();
        Integer saturationStrength = idPhotoProcessDto.getSaturationStrength();
        File inputImage = idPhotoProcessDto.getInputImage();
        String inputImageBase64 = idPhotoProcessDto.getInputImageBase64();
        Integer height = idPhotoProcessDto.getHeight();
        Integer width = idPhotoProcessDto.getWidth();
        Boolean hd = idPhotoProcessDto.getHd();
        Integer dpi = idPhotoProcessDto.getDpi();

        ThrowUtil.throwIf(Objects.isNull(inputImage) && StrUtil.isBlank(inputImageBase64),
                ErrorEnum.UPLOAD_FILE_EMPTY, "图片为空");

        HashMap<String, Object> paramMap = new HashMap<>();
        if (Objects.nonNull(inputImage)) {
            paramMap.put("input_image", inputImage);
//            paramMap.put("input_image_base64", Base64.encode(inputImage));
        }
        if (StrUtil.isNotBlank(inputImageBase64)) {
            paramMap.put("input_image_base64", inputImageBase64);
        }
        paramMap.put("height", height);
        paramMap.put("width", width);
        paramMap.put("hd", hd);
        paramMap.put("dpi", dpi);
        paramMap.put("face_alignment", faceAlignment);
        paramMap.put("head_measure_ratio", headMeasureRatio);
        paramMap.put("head_height_ratio", headHeightRatio);
        paramMap.put("top_distance_max", topDistanceMax);
        paramMap.put("top_distance_min", topDistanceMin);
        paramMap.put("brightness_strength", brightnessStrength);
        paramMap.put("contrast_strength", contrastStrength);
        paramMap.put("sharpen_strength", sharpenStrength);
        paramMap.put("saturation_strength", saturationStrength);

        ProcessResult processResult = null;
        String url = ID_PHOTO_URL_PRE + ID_PHOTO;
        String response = null;
        try {
            response = HttpRequest.post(url)
                    .form(paramMap)
                    .timeout(5000)
                    .execute().body();
            processResult = JSONUtil.toBean(response, ProcessResult.class);
        } catch (Exception e) {
            log.error("request fail:{}", e.getMessage());
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "透明证件照生成失败");
        }

        if (processResult == null || Boolean.FALSE.equals(processResult.isStatus())) {
            log.error("response fail");
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "透明证件照生成失败");
        }

        return processResult;
    }

    public ProcessResult addBackgroundColor(BackgroundProcessDto backgroundProcessDto) {
        ProcessResult processResult = null;
        String color = backgroundProcessDto.getColor();
        String inputImageBase64 = backgroundProcessDto.getInputImageBase64();
        HashMap<String, Object> paramsMap = new HashMap<>();
        paramsMap.put("color", color);
        paramsMap.put("input_image_base64", inputImageBase64);

        String url = ID_PHOTO_URL_PRE + ADD_BACKGROUND;
        String response = null;

        try{
            response = HttpRequest.post(url)
                    .form(paramsMap)
                    .timeout(5000)
                    .execute().body();
            processResult = JSONUtil.toBean(response, ProcessResult.class);
        }catch (Exception e){
            log.error("request fail:{}", e.getMessage());
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "证件照生成失败");
        }

        if (processResult == null || Boolean.FALSE.equals(processResult.isStatus())) {
            log.error("response fail");
            throw new BusinessException(ErrorEnum.SYSTEM_ERROR, "证件照生成失败");
        }

        return processResult;
    }


    public static void main(String[] args) {

        File image = FileUtil.file("C:\\test1.png");
        MattingProcessDto mattingProcessDto = new MattingProcessDto();
        mattingProcessDto.setInputImage(image);
        PictureProcessApi pictureProcessApi = new PictureProcessApi();
        System.out.println(pictureProcessApi.humanMatting(mattingProcessDto));

    }
}
